<template>
  <div>
    <van-nav-bar :title="receiver.nickname" left-arrow @click-left="onClickLeft"
      class="vant_search"/>
    <!-- -------------------------------------- -->
    <div class="main">
      <!-- <h5 style="text-align: center;clear:both;margin:0 0 5px 0;">{{msgDataList[0].timestamp}}</h5> -->
      <template v-for="item in msgDataList" :key="item">
        <div v-if="item.receiver=== this.recerId" class="chat-bubble chat-bubble-left">
          <img :src="this.receiver.headImg" alt="" srcset="">
          <span>{{ item.content }}</span>
        </div>
        <div v-else class="chat-bubble chat-bubble-right">
          <img :src="this.userInfo.headImg" alt="" srcset="">
          <span>{{ item.content }}</span>
        </div>
      </template>
      <h5 style="text-align: center;clear:both;margin:0 0 5px 0;">{{this.getTime()}}</h5>
      <template v-for="item in list" :key="item">
        <div v-if="item.left" class="chat-bubble chat-bubble-left">
          <img :src="this.receiver.headImg" alt="" srcset="">
          <span>{{ item.left.content }}</span>
        </div>
        <div v-else class="chat-bubble chat-bubble-right">
          <img :src="this.userInfo.headImg" alt="" srcset="">
          <span>{{ item.right.msg }}</span>
        </div>
      </template>
    </div>
    <!-- ------------------------------ -->
    <div class="footer">
      <van-field v-model="message" autosize type="textarea" placeholder="请输入留言">
        <template #button>
          <template v-if="!this.message">
            <van-icon size="25px" name="add-o" />
          </template>
          <template v-else>
            <van-button size="mini" round type="success" @click="send()">
              发&nbsp;&nbsp;送</van-button
            >
          </template>
        </template>
      </van-field>
    </div>
  </div>
</template>

<script>
import { sendMessage,messageList } from "@/api/request/sedMessage.js";
import VantNavbar from "@/components/VantNavbar.vue";

export default {
  components: { VantNavbar },
  data() {
    return {
      list: [],
      msgDataList: [],
      userInfo: this.$store.state.userInfo, //当前登录的用户信息
      message: undefined, //发送的内容
      receiver: this.$route.params, // 信息接收者
      recerId: this.$route.params.id, //接收者id
      messageList: [], //发送的信息
      recerMsgList: [], //接收到的信息
    };
  },
  created() {
    this.getMessageList();
    this.connect();
  },
  mounted() {
    document.onkeydown = () => {
      var key = window.event.keyCode;
      if(key == 13) {
        this.send();
      }
    }
  },
  methods: {
    getMessageList() {
      let par = {
        limit: 100,
        sender: this.userInfo.userId,//发送人
        receiver: this.recerId,//接收人
      }
      // console.log('------', par);
      messageList(par).then(res => {
        // console.log(res.data.data);
        this.msgDataList = res.data.data;
      }).catch(err => {
        alert(err)
      })
    },
    connect() {
      // 链接
      // console.log("1.开始链接,创建socket");
      manualStop = false;
      window.localStorage.account = "";
      this.socket = new WebSocket(CIM_URI);
      this.socket.cookieEnabled = false;
      this.socket.binaryType = "arraybuffer";
      this.socket.onopen = this.innerOnConnectFinished;
      this.socket.onmessage = this.innerOnMessageReceived;
      this.socket.onclose = this.innerOnConnectionClosed;
    },
    innerOnConnectFinished() {
      // 链接成功回调
      // console.log("进入链接成功回调方法");
      let account = window.localStorage.account;
      if (account === "" || account === undefined) {
        account = this.userInfo.userId;
        // account = this.username;
      }
      this.bind(account);
    },
    innerOnMessageReceived(e) {
      // 接收到消息回调
      // console.log("socket触发接收消息时间,判断消息类型进行处理");
      let data = new Uint8Array(e.data);
      let type = data[0];
      let body = data.subarray(DATA_HEADER_LENGTH, data.length);

      // 判断消息类型
      if (type === PING) {
        // console.log("消息类型--未知");
        this.pong();
        return;
      } else if (type === MESSAGE) {
        // 消息
        // console.log("消息类型--普通消息");
        let message =
          proto.com.farsunset.cim.sdk.web.model.Message.deserializeBinary(body);
        this.onInterceptMessageReceived(message.toObject(false));
        return;
      } else if (type === REPLY_BODY) {
        // 账号绑定成功通知
        // console.log("消息类型--绑定账号成功通知");
        let message =
          proto.com.farsunset.cim.sdk.web.model.ReplyBody.deserializeBinary(
            body
          );
        /**
         * 将proto对象转换成json对象，去除无用信息
         */
        let reply = {};
        reply.code = message.getCode();
        reply.key = message.getKey();
        reply.message = message.getMessage();
        reply.timestamp = message.getTimestamp();
        reply.data = {};
        /**
         * 注意，遍历map这里的参数 value在前key在后
         */
        message.getDataMap().forEach(function (v, k) {
          reply.data[k] = v;
        });
        if (reply.key === "client_bind" && reply.code === "200") {
          console.log("账号绑定成功");
        }
      }
    },
    innerOnConnectionClosed() {
      // 链接中断回调
      // 中断后循环进行重连
      if (!manualStop) {
        let time = Math.floor(Math.random() * (30 - 15 + 1) + 15);
        setTimeout(function () {
          this.connect();
        }, time);
      }
    },
    bind(account) {
      // 绑定账号
      // console.log("进入绑定账号方法");
      window.localStorage.account = account;
      let deviceId = window.localStorage.deviceId;
      if (deviceId === "" || deviceId === undefined) {
        deviceId = generateUUID();
        window.localStorage.deviceId = deviceId;
      }
      let browser = getBrowser();
      let body = new proto.com.farsunset.cim.sdk.web.model.SentBody();
      body.setKey("client_bind");
      body.setTimestamp(new Date().getTime());
      body.getDataMap().set("uid", account);
      body.getDataMap().set("channel", APP_CHANNEL);
      body.getDataMap().set("appVersion", APP_VERSION);
      body.getDataMap().set("osVersion", browser.version);
      body.getDataMap().set("packageName", APP_PACKAGE);
      body.getDataMap().set("deviceId", deviceId);
      body.getDataMap().set("deviceName", browser.name);
      body.getDataMap().set("language", navigator.language);
      this.sendRequest(body);
    },
    sendRequest(body) {
      // 通过websocket绑定用户
      // console.log("发送绑定账号请求");
      let data = body.serializeBinary();
      let protobuf = new Uint8Array(data.length + 1);
      protobuf[0] = SENT_BODY;
      protobuf.set(data, 1);
      this.socket.send(protobuf);
    },
    pong() {
      let pong = new Uint8Array(PONG_BODY.byteLength + 1);
      pong[0] = PONG;
      pong.set(PONG_BODY, 1);
      this.socket.send(pong);
    },
    onInterceptMessageReceived(message) {
      // 判断消息类型,做不同的处理
      console.log("进入普通消息处理方法");
      /*
       * 被强制下线之后，不再继续连接服务端
       */
      if (message.action === ACTION_999) {
        manualStop = true;
      }
      //账户在其他地方登录了
      if (message.action === ACTION_999) {
        console.log("你的账号在其他地方登录了!");
        return;
      }
      // console.log("你接收到一条消息,消息内容:::", message.content);
      console.log("接收的消息", message);
      // this.recerMsgList.push(message);
      this.list.push({
        left: {...message}
      })
    },
    //发送消息
    send() {
      if (!this.message.trim().length) {
        return;
      }
      // console.log(this.userInfo.userId);
      let par = {
        content: this.message,
        action: 2,
        sender: "system",
        receiver: this.recerId,
        format: "0",
      };
      sendMessage(par)
        .then((res) => {
          if (res.status === 200) {
            this.list.push({
              right: {
                time: this.getTime(),
                msg: res.data.data.content,
              }
            })
          }
        })
        .catch((err) => {
          alert(err);
        });
      this.message = undefined;
    },
    getTime(date) {
      if (!date) {
        var date = new Date();
        // console.log("发送时间", date);
      } else {
        var date = date;
        // console.log("接收时间", date);
      }
      var Y = date.getFullYear() + "-";
      var M =
        (date.getMonth() + 1 < 10
          ? "0" + (date.getMonth() + 1)
          : date.getMonth() + 1) + "-";
      var D =
        (date.getDate() < 10 ? "0" + date.getDate() : date.getDate()) + " ";
      var H =
        (date.getHours() < 10 ? "0" + date.getHours() : date.getHours()) + ":";
      var m =
        (date.getMinutes() < 10 ? "0" + date.getMinutes() : date.getMinutes()) +
        ":";
      var s =
        date.getSeconds() < 10 ? "0" + date.getSeconds() : date.getSeconds();
      var datetime = Y + M + D + H + m + s;
      // console.log(datetime);
      return datetime;
    },
    onClickLeft() {
      this.$router.push({ name: "weChat" });
    },
  },
};
</script>

<style scoped>
body {
  height: 100vh;
  margin: 0;
  padding: 0;
  background-color: grey;
}
.main {
  overflow: scroll;
  position: fixed;
  top: 50px;
  margin: 0 0 0 15px;
  width: 92%;
  height: 88%;
}
.msg_list {
  width: 90%;
  margin: 0;
}

.chat-bubble {
  color: #333;
  border-radius: 5px;
  box-shadow: 3px 5px 15px rgba(0, 0, 0, 0.2);
  padding: 5px 10px;
  width: auto;
  max-width: 50%;
  text-align: left;
  display: inline-block !important;
  position: relative;
  word-break: break-all;
  background-color: rgb(255, 252, 252);
  transition: all 0.2s;
  cursor: pointer;
  clear: both;
  margin-bottom: 5px;
}
.chat-bubble-left {
  float: left;
  left: 40px;
}
.chat-bubble-left::before {
  position: absolute;
  content: "";
  left: -10px;
  border-top: 10px solid transparent;
  border-bottom: 10px solid transparent;
  border-right: 11px solid rgb(252, 251, 251);
}
.chat-bubble-left img {
  height: 25px;
  width: 25px;
  position: absolute;
  left: -40px;
  top: -3px;
}
.chat-bubble-right {
  float: right;
  background: #519c2b;
  color: #ffffff;
  right: 40px;
}
.chat-bubble-right::before {
  position: absolute;
  content: "";
  right: -10px;
  border-top: 10px solid transparent;
  border-bottom: 10px solid transparent;
  border-left: 11px solid #519c2b;
}
.chat-bubble-right img {
  height: 25px;
  width: 25px;
  position: absolute;
  right: -40px;
  top: -3px;
}
.footer {
  position: fixed;
  bottom: 0;
  width: 100%;
}
.van-cell {
  padding: 0 5px;
}
</style>